/*
 * To change this template, choose Tools | Templates
 * and open the template in the editor.
 */

package Services;

import database.daos.ClientHistoryDAO;
import database.daos.UserDAO;
import Services.exception.ExistenceAccountException;
import Services.exception.EntityNotFoundException;
import Services.exception.InvalidAmountOperationException;
import Services.exception.InvalidPasswordException;
import Services.exception.ServiceException;
import Services.exception.UnableToConnectException;
import Validations.UserValidation;
import beans.ClientHistoryBean;
import beans.UserBean;
import database.daos.DAOException;
import java.sql.Blob;


/**
 *
 * @author Anthar
 */
public class UserServices {

    private UserValidation userValidation;
    private UserDAO userDAO;
    private ClientHistoryDAO clientHistoryDAO;

    public UserServices(){
        userValidation = new UserValidation();
        userDAO = new UserDAO();
        clientHistoryDAO = new ClientHistoryDAO();
    }

    public UserBean searchUser(String userAccountName) throws ServiceException{
      try {
              return getUserDAO().searchUser(userAccountName);
            } catch (DAOException ex) {
                throw new UnableToConnectException(ex.getMessage());
            }
    }

    public UserBean searchUserByFingerPrint(Blob fingerPrint)throws ServiceException{
        try{
            return getUserDAO().searchByFingerPring(fingerPrint);
         } catch (DAOException ex) {
            throw new UnableToConnectException(ex.getMessage());
         }
    }
    

    public double getUserAmmount(String userAccountName) throws ServiceException{
        try {
            return getUserDAO().getUserAmount(userAccountName);
        } catch (DAOException ex) {
            throw new UnableToConnectException(ex.getMessage());
        }
        
    }

   public void transferAmount(String userAccountName, double amount, String accountToTransfer) throws ServiceException{
           final double actualUserAmmount = getUserAmmount(userAccountName);

           if (getUserValidation().existUserAccount(accountToTransfer)) {
                if(getUserValidation().isValidTransferAmountOperation(actualUserAmmount, amount)){
                     decreaseAmountUserAccount(userAccountName, amount);
                     transferAmountIntoAccount(accountToTransfer, amount);
                }else{
                    throw new InvalidAmountOperationException();
                }
            }else{
                throw new EntityNotFoundException("User");
            }
       
     }

   
    public ClientHistoryBean getClientHistory(String userAccountName) throws ServiceException {
        try {
            final UserBean userInformation = searchUser(userAccountName);
            return getClientHistoryDAO().getClientHistory(userInformation.getUserId());
        } catch (DAOException ex) {
            throw new UnableToConnectException(ex.getMessage());
        } 
    }

    public UserBean userLogginByPassword(String userAccountName, String password) throws ServiceException{
            
          if (getUserValidation().existUserAccount(userAccountName)) {
                UserBean userInfo = searchUser(userAccountName);
                String userPassword = userInfo.getUserAccountPassword();
                if (userPassword.equals(password)) {
                        return userInfo;
                } else {
                       throw new InvalidPasswordException();
                }
            } else {
                throw new EntityNotFoundException("User");
            }
    }


    public UserBean userLogginByFingerPrint(Blob fingerPrint)throws ServiceException{
          UserBean userInfo = searchUserByFingerPrint(fingerPrint);
          return userInfo;
    }
    
    
     public void modifyUserAccount(UserBean userInfo) throws ServiceException{
            
            final String ACTUAL_ACCOUNT = getActualUserAccount(userInfo.getUserFirstName(),userInfo.getUserLastName1());
            final boolean existAccount =getUserValidation().existUserAccount(userInfo.getUserAccountName());
            final boolean sameAccount = getUserValidation().isCoincidenceAccount(ACTUAL_ACCOUNT, userInfo);
            
            if(sameAccount || !existAccount){
              try {
                   getUserDAO().modifyUserInformation(userInfo);
                } catch (DAOException ex) {
                   throw new UnableToConnectException(ex.getMessage());
                }
            }
            else{
                throw new ExistenceAccountException();
            }
     }

   
     
     /*****************
      * PRIVATE METOHDS
      *****************/

      public void decreaseAmountUserAccount(String userAccountName , double amount) throws ServiceException {
        try {
            getUserDAO().decreaseAmount(userAccountName, amount);
        } catch (database.daos.DAOException ex) {
            throw new UnableToConnectException(ex.getMessage());
        }

    }

    private void transferAmountIntoAccount(String accountToTransfer, double amount) throws ServiceException{
        try {
            getUserDAO().insertAmmount(accountToTransfer, amount);
        } catch (database.daos.DAOException ex) {
            throw new UnableToConnectException(ex.getMessage());
        }

    }
  
  private String getActualUserAccount(String firstName, String lastName) throws ServiceException{
        try {
            return getUserDAO().getActualUserAccount(firstName, lastName);
        } catch (database.daos.DAOException ex) {
           throw new UnableToConnectException(ex.getMessage());
        }
    }



    /******************
     * GETS Y SETS
     *****************/

    /**
     * @return the userValidation
     */
    public UserValidation getUserValidation() {
        return userValidation;
    }

    /**
     * @return the userDAO
     */
    public UserDAO getUserDAO() {
        return userDAO;
    }

    /**
     * @return the clientHistoryDAO
     */
    public ClientHistoryDAO getClientHistoryDAO() {
        return clientHistoryDAO;
    }

    /**
     * @param clientHistoryDAO the clientHistoryDAO to set
     */
    public void setClientHistoryDAO(ClientHistoryDAO clientHistoryDAO) {
        this.clientHistoryDAO = clientHistoryDAO;
    }
      


}
